<?php

namespace PKApp\Content\Classes;

use PKApp\Model\Classes\TraitModel;
use PKFrame\DataHandler\Arrays;
use PKFrame\Service;

class ContentService extends Service
{

    use TraitModel;

    protected $model_id, $table_name;

    public function __construct($model_id)
    {
        parent::__construct();
        $this->model_id = $model_id;
        $this->table_name = $this->serviceOfModel()->GetTableNameByModelId($model_id);
    }

    public function BatchInsertByContent(array $list_base, array $list_data)
    {
        $this->BatchInsert($list_base);
        $this->BatchInsert($list_data, $this->table_name . '_data');
    }

    public function GetSortModeList(): array
    {
        return dict('category_content_orderList');
    }

    public function interface_getEntityById($id, $viewField = '*')
    {
        return $this->getEntityById($id, 'Content_idEmpty', 'Content_Empty', $viewField);
    }

    protected function db(): ContentDataBase
    {
        return new ContentDataBase($this->table_name);
    }

    private function _paramsOfQuery(array &$viewParams)
    {
        array_key_exists('isDeleted', $viewParams) ?: $viewParams['isDeleted'] = 0;
        if (array_key_exists('query_like', $viewParams)) {
            $query = $viewParams['query_like'];
            !Arrays::Is($query) ?: $query = implode('|', $query);
            unset($viewParams['query_like']);
            $viewParams[] = ['CONCAT_WS(`title`, `seoTitle`,`seoKeywords`)', 'REGEXP', $query];
        }
    }

    public function GetCount(array $viewParams = []): int
    {
        $this->_paramsOfQuery($viewParams);
        return $this->_getCount($viewParams);
    }

    private function _getCount(array $viewParams = []): int
    {
        return $this->db()->Where($viewParams)->Count();
    }

    public function GetList($viewParams = [], $viewField = '*', $index = 0, $lineNum = 0, $orderBy = null)
    {
        if (is_array($orderBy) && $orderBy['field'] == 'catListSort') {
            return $this->db()->GetListByCatSort($viewParams, $lineNum, $index);
        } else {
            $this->_paramsOfQuery($viewParams);
            return $this->_getList($viewParams, $viewField, $index, $lineNum, $orderBy);
        }
    }

    private function _getList($viewParams = [], $viewField = '*', $index = 0, $lineNum = 0, $orderBy = null)
    {
        $db = $this->db();
        if (is_array($orderBy)) {
            $db->OrderBy($orderBy['field'], $orderBy['mode']);
            if ($orderBy['field'] == 'toTop') {
                $db->OrderBy('id');
            }
        } else {
            $db->OrderBy('listSort')
                ->OrderBy('id');
        }
        if ($lineNum > 0) {
            $db->Limit($lineNum, $index);
        }
        return $db->Where($viewParams)
            ->Select($viewField)->ToList();
    }

    public function GetEntity($viewParams = [], $viewField = '*'): array
    {
        if (!(request()->controller() == 'AdminGetContent' && request()->action() == 'ApiGetDetail')) {
            array_key_exists('isDeleted', $viewParams) ?: $viewParams['isDeleted'] = 0;
        }
        $entity = $this->db()->GetDetail($viewParams, $viewField);
        Arrays::Is($entity) ?: $this->noticeByJson('Content_Empty');
        $result = $this->modelOfToOutData()->Get($entity, $this->model_id);
        // 内容分页
        if (request()->controller() == 'Content'
            && $this->modelOfToOutData()->pageSize > 0) {
            $result['pageSize'] = $this->modelOfToOutData()->pageSize;
        }
        return $result;
    }

    public function GetEntityByPageIndex($index, $params_where = []): array
    {
        static $entity;
        is_array($entity) ?: $entity = $this->db()->GetDetailByPageIndex($index, $params_where);
        $result = $this->modelOfToOutData()->Get($entity, $this->model_id);
        // 内容分页
        if ($this->modelOfToOutData()->pageSize > 0) {
            $result['pageSize'] = $this->modelOfToOutData()->pageSize;
        }
        return $result;
    }

    public function GetContentUpOrNext($viewParams, $order_field, $order_mode)
    {
        return $this->db()->GetContentUpOrNext($viewParams, $order_field, $order_mode);
    }

    public function SaveData($params, $id = 0): ?int
    {
        if ($this->serviceOfModel()->GetUniqueTitle($this->model_id)) {
            $params_query = ['title' => $params['base']['title']];
            $id == 0 ?: $params_query[] = ['id', '!=', $id];
            $entity = $this->db()->Where($params_query)->Select('*')->First();
            !Arrays::Is($entity) ?: $this->noticeByJson('Exists_title_unique');
        }
        return $this->db()->SaveData($params, $id);
    }

    public function CopyToOtherCategory(array $from_list, int $toCategoryId, int $siteId)
    {
        $id_list = Arrays::Column($from_list, 'id');
        $from_listByData = $this->db()->GetListByData($id_list);
        $new_dataList = [];
        if (Arrays::Is($from_list)) {
            foreach ($from_list as $item) {
                $tmp_contentId = $item['id'];
                $item['catId'] = $toCategoryId;
                $item['siteId'] = $siteId;
                unset($item['id']);
                $tmp_data = array_filter($from_listByData, function ($item) use ($tmp_contentId) {
                    return $item['id'] == $tmp_contentId ? $item : [];
                });
                if (count($tmp_data) == 1) {
                    // 判断在列表中同 id 的数据
                    $tmp_data = array_shift($tmp_data);
                    // 获得新 id
                    $tmp_data['id'] = $this->Add($item);
                    $new_dataList[] = $tmp_data;
                }
            }
        }
        if (Arrays::Is($new_dataList)) {
            $this->db()->CopyToOtherCategoryByDataList($new_dataList);
        }
    }

    public function TruncateByContent()
    {
        $this->db()->TruncateByContent();
    }

    public function ReplaceFieldContent(array $list_field, string $search, string $replace, bool $is_list)
    {
        $replace_str = '';
        foreach ($list_field as $field) {
            $replace_str .= '`' . $field . '`=REPLACE(`' . $field . '`,\'' . $search . '\',\'' . $replace . '\'),';
        }
        $this->db()->ReplaceFieldContent(rtrim($replace_str, ','), $is_list);
    }

}